package com.hxzy.tms.service.impl;

import java.security.SecureRandom;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.Random;

import org.apache.commons.codec.digest.DigestUtils;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.hxzy.tms.dao.UserDao;
import com.hxzy.tms.entity.User;
import com.hxzy.tms.service.ServiceResult;
import com.hxzy.tms.service.UserService;
import com.hxzy.tms.session.SessionHolder;

public class UserServiceImpl implements UserService {
    private Logger logger=LoggerFactory.getLogger(getClass());
    private UserDao userDao;

    public ServiceResult<User> register(String email, String passwd, String nickname, String realname, long mobile,
            String emailVerification, String ip) {
        Map<String, Object> param = new HashMap<String, Object>();
        param.put("email", email);
        List<User> users = userDao.read("from User where email = :email", param);
        if (!users.isEmpty()) {
            return new ServiceResult<User>(-1,null,"邮箱已经存在");
        }
        param = new HashMap<String, Object>();
        param.put("phone", mobile);
        users = userDao.read("from User where phone = :phone", param);
        if (!users.isEmpty()) {
            return new ServiceResult<User>(-2,null,"该手机号码已注册");
        }
        String randomUsername = this.generateUsername(ip).data;
        if (randomUsername == null) {
            return new ServiceResult<User>(-3,null,"用户名创建失败");
        }
        User user = new User();
        user.setSalt(createSalt());
        user.setUsername(randomUsername);
        user.setEmail(email);
        user.setPasswd(DigestUtils.sha256Hex((user.getSalt() + passwd).getBytes()));
        user.setNickname(nickname);
        user.setRealname(realname);
        user.setPhone(mobile);
        user.setGmtCreate(System.currentTimeMillis() / 1000);
        user.setGmtModified(user.getGmtCreate());
        user.setIpReg(ip);
        user.setStatus(1L);
        userDao.create(user);
        logger.info("用户注册 {}", user.getUsername());
        return new ServiceResult<User>(1,null,"注册成功");
    }

    public ServiceResult<String> generateUsername(String ip) {
        int i = 3;
        while (i-- > 0) {
            String username = "u" + (System.currentTimeMillis() + (new Random().nextInt(10000)));
            Map<String, Object> param = new HashMap<String, Object>();
            param.put("username", username);
            List<User> users = userDao.read("from User where username = :username", param);
            if (users.isEmpty()) {
                return new ServiceResult<String>(1, username); // 邮箱已存在
            }
        }
        return null;
    }
    
    private String createSalt() {
        Random ranGen = new SecureRandom();
        byte[] aesKey = new byte[32];
        ranGen.nextBytes(aesKey);
        StringBuffer hexString = new StringBuffer();
        for (int i = 0; i < aesKey.length; i++) {
            String hex = Integer.toHexString(0xff & aesKey[i]);
            if (hex.length() == 1)
                hexString.append('0');
            hexString.append(hex);
        }
        return hexString.toString();
    }
    
    public User login(String email, String passwd, String ip) {
        try {
            User user = userDao.get(email);
            if (user == null || !user.getPasswd().equals(DigestUtils.sha256Hex((user.getSalt() + passwd).getBytes()))) {
                return null;
            }
            long now=(System.currentTimeMillis()/1000);
            user.setGmtLogin(now);
            user.setIpLogin(ip);
            user.setGmtModified(now);
            userDao.saveOrUpdate(user);
            return user;
        } catch (Exception e) {
            logger.error("登陆失败",e);
        }
        return null;
    }

    public ServiceResult<String> generateSessionHash(String ip) {
        
        return null;
    }
    public ServiceResult<User> getUser(String hash, String ip) {
        if (StringUtils.isBlank(hash) || StringUtils.isBlank(ip)) {
            return new ServiceResult<User>(1, null);
        }
        if (SessionHolder.get() != null) {
            return new ServiceResult<User>(1, SessionHolder.get());
        }

        if (StringUtils.isEmpty(ip) || StringUtils.isEmpty(hash)) {
            return new ServiceResult<User>(1, null);
        }

        Map<String, Object> param = new HashMap<String, Object>();
        param.put("hash", hash);
        param.put("gmt_hash_expires", (System.currentTimeMillis() / 1000));
        List<User> users = userDao.read("from User where hash = :hash and gmtHashExpires > :gmt_hash_expires ", param);
        if (users.isEmpty()) {
            return new ServiceResult<User>(1, null);
        }

        User user = users.get(0);

        if (!ip.equals(user.getIpLogin())) { // 如果换 ip 了就当没有登录过啦，TODO 要清空 hash
            return new ServiceResult<User>(1, null);
        }

        User userInSession = new User();
        userInSession.setId(user.getId());
        userInSession.setNickname(user.getNickname());
        return new ServiceResult<User>(1, userInSession);
    }

    public UserDao getUserDao() {
        return userDao;
    }

    public void setUserDao(UserDao userDao) {
        this.userDao = userDao;
    }
}